package com.zdkj.subway.stm.service.impl;

import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.zdkj.common.core.constant.CommonConstants;
import com.zdkj.common.security.util.ObjectUtils;
import com.zdkj.subway.stm.constant.StmConstans;
import com.zdkj.subway.stm.dto.in.SwStTicketHandInputDTO;
import com.zdkj.subway.stm.dto.in.SwStTicketRecoveryDTO;
import com.zdkj.subway.stm.dto.out.SwStTicketHandDetailsDTO;
import com.zdkj.subway.stm.entity.SwStTicketHand;
import com.zdkj.subway.stm.entity.SwStTicketHandDetail;
import com.zdkj.subway.stm.mapper.SwStTicketHandMapper;
import com.zdkj.subway.stm.service.SwStTicketHandDetailService;
import com.zdkj.subway.stm.service.SwStTicketHandService;
import lombok.AllArgsConstructor;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.servlet.http.HttpServletResponse;
import java.io.BufferedInputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.net.URLEncoder;
import java.util.List;

/**
 * 车票上交主表
 *
 * @author cuilei
 * @date 2020-05-26 15:03:29
 */
@Service
@AllArgsConstructor
public class SwStTicketHandServiceImpl extends ServiceImpl<SwStTicketHandMapper, SwStTicketHand> implements SwStTicketHandService {
    private final SwStTicketHandDetailService swStTicketHandDetailService;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean savePrimaryAndDetails(Object obj) {
        SwStTicketHand defaultObj = ObjectUtils.getDefaultObj(SwStTicketHand.class);
        List<SwStTicketHandDetail> swStTicketHandDetails = null;

        if (obj instanceof SwStTicketHandInputDTO) {
            defaultObj.setDataSource(StmConstans.TICKET_HAND_DATASOURCE_STATION);
            SwStTicketHandInputDTO swStTicketHandInput = (SwStTicketHandInputDTO) obj;
            swStTicketHandDetails = swStTicketHandInput.getSwStTicketHandDetails();
            BeanUtils.copyProperties(swStTicketHandInput, defaultObj);
            //车站自己添加的数据，默认通知状态置成已通知且已确认
            defaultObj.setNoticeStatus(CommonConstants.INFORMED);
            defaultObj.setNoticeConfirm(CommonConstants.CONFIRM);
            defaultObj.setHandStatus(CommonConstants.UN_CONFIRM);

            int totalCount = swStTicketHandDetails.stream()
                    .mapToInt(SwStTicketHandDetail::getHandCount).sum();
            defaultObj.setHandCount(totalCount);
        }

        if (obj instanceof SwStTicketRecoveryDTO) {
            defaultObj.setDataSource(StmConstans.TICKET_HAND_DATASOURCE_LINE);
            SwStTicketRecoveryDTO swStTicketRecovery = (SwStTicketRecoveryDTO) obj;
            swStTicketHandDetails = swStTicketRecovery.getSwStTicketHandDetails();
            BeanUtils.copyProperties(swStTicketRecovery, defaultObj);
            //线网添加的车票回收信息，数据默认同步，车站无需提交，此处默认添加数据就是已提交状态
            defaultObj.setSubmitStatus(CommonConstants.SUBMIT);
            //线网添加的车票回收信息，默认通知状态置成未通知且未确认
            defaultObj.setNoticeStatus(CommonConstants.UN_INFORMED);
            defaultObj.setNoticeConfirm(CommonConstants.UN_CONFIRM);
            defaultObj.setHandStatus(CommonConstants.UN_CONFIRM);

            int totalCount = swStTicketHandDetails.stream()
                    .mapToInt(SwStTicketHandDetail::getReceiveCount).sum();
            defaultObj.setReceiveCount(totalCount);
        }

        if (null == swStTicketHandDetails) {
            return false;
        } else {
            SwStTicketHand swStTicketHand = new SwStTicketHand();
            BeanUtils.copyProperties(defaultObj,swStTicketHand);

            swStTicketHand.setLineCode(defaultObj.getLineCode());
            swStTicketHand.setStationCode(defaultObj.getStationCode());
            save(defaultObj);
            swStTicketHand.setId(defaultObj.getId());
            updateById(swStTicketHand);// TODO 处理线路站点存不进去
            swStTicketHandDetails.forEach(item -> item.setRefId(swStTicketHand.getId()));
            return swStTicketHandDetailService.saveBatch(swStTicketHandDetails);
        }
    }

    @Override
    public SwStTicketHandDetailsDTO getDetailById(Integer id) {
        SwStTicketHandDetailsDTO mainAndItems = new SwStTicketHandDetailsDTO();
        mainAndItems.setSwStTicketHand(getById(id));
        List<SwStTicketHandDetail> list = swStTicketHandDetailService.list(Wrappers.<SwStTicketHandDetail>query()
                .lambda().eq(SwStTicketHandDetail::getRefId, id));
        //配送和回收车票名称显示字段共用
        for (SwStTicketHandDetail swStTicketHandDetail : list) {
            swStTicketHandDetail.setTicketTypeParam(swStTicketHandDetail.getTicketName());
        }
        mainAndItems.setSwStTicketHandDetails(list);
        return mainAndItems;
    }
    /**
     * 车票回收信息模板下载
     * @param
     * @return
     * @throws
     */
    @Override
    public void exportTamplateRecovery(HttpServletResponse response) {
        String  verifyConfirmName = "车票回收信息模板";
        String  tableName = "sw_st_ticket_recovery";

        BufferedInputStream br = null;
        OutputStream out = null;
        try {
            response.reset(); // 非常重要
            response.setContentType("application/vnd.ms-excel");
            response.setCharacterEncoding("utf-8");
            final String fileName = URLEncoder.encode(verifyConfirmName, "UTF-8");
            response.setHeader("Content-disposition", "attachment;filename=" + fileName + System.currentTimeMillis() + ".xlsx");

            br =  new BufferedInputStream(this.getClass().getResourceAsStream("/static/excel/template/import/" + tableName + ".xlsx"));

            byte[] buf = new byte[1024];
            int len = 0;

            out = response.getOutputStream();
            while ((len = br.read(buf)) > 0) {
                out.write(buf, 0, len);
            }

        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            if(out != null) {
                try {
                    out.close();
                } catch (IOException ioe) {
                    ioe.printStackTrace();
                }
            }
            if(br != null){
                try {
                    br.close();
                } catch (IOException ioe) {
                    ioe.printStackTrace();
                }
            }
        }
    }
}
